package net.zui.action;

import java.awt.event.KeyEvent;
import java.awt.event.MouseEvent;
import java.awt.event.MouseWheelEvent;
import java.awt.event.WindowEvent;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import net.zui.annotation.Action;
import net.zui.entity.ZAction;
import net.zui.entity.ZBaseManager;
import net.zui.enume.ActionEnum;
import net.zui.inter.IGroup;

public class ActionDispather {
	protected IGroup group;
	
	protected Map<ZAction,Method> map=new HashMap<>();
	protected List<ZAction> list=new ArrayList<>();
	protected ZBaseManager manager;
	
	public ActionDispather(IGroup group) {
		this.group=group;
		manager=group.getManager();
	}
	
	public boolean regAction(Object obj) {
		if(obj==null)return false;
		Method[] methods = obj.getClass().getMethods();
		
		Action e;
		ZAction za;
		ActionEnum num;
		for(Method m:methods) {
			e=m.getAnnotation(Action.class);
			if(e!=null) {
				num=e.action();
				for(String id:e.id()) {
					za=new ZAction(id, num, obj);
					map.put(za, m);
					list.add(za);
				}
			}
		}
		return true;
	}
	
	public boolean fire(String id,ActionEnum num,Object... args) {
		ZAction find=null;
		for(ZAction za:list) {
			if(za.getId().equals(id) && za.getAction()==num) {
				find=za;
				break;
			}
		}
		boolean res;
		if(find!=null) {
			Method method = map.get(find);
			try {
				method.invoke(find.getSource(), args);
			} catch (IllegalAccessException e) {
				e.printStackTrace();
			} catch (IllegalArgumentException e) {
				e.printStackTrace();
			} catch (InvocationTargetException e) {
				e.printStackTrace();
			}
			res=true;
		}else {
			res=false;
		}
		return res;
	}
	
	/**
	   * 调用本窗体事件，其id固定为‘this’
	 * @param num 事件类型
	 * @param e 事件信息对象
	 * @return true-调用事件成功
	 */
	public boolean windowEventFire(ActionEnum num,WindowEvent e) {
		if(!num.toString().startsWith("window"))return false;
		return fire("this",num,e);
	}
	
	/**
	   * 调用本窗体或组件的按键事件，其窗体id固定为this
	 * @param id 组件id或‘this’
	 * @param num 事件类型
	 * @param e 事件信息对象
	 * @return true-调用事件成功
	 */
	public boolean keyEventFire(String id,ActionEnum num,KeyEvent e) {
		if(!num.toString().startsWith("key"))return false;
		return fire(id,num,e);
	}
	
	/**
	   * 调用本窗体或组件的鼠标事件，其窗体id固定为this
	 * @param id 组件id或‘this’
	 * @param num 事件类型
	 * @param e 事件信息对象
	 * @return true-调用事件成功
	 */
	public boolean mouseEventFire(String id,ActionEnum num,MouseEvent e) {
		if(!num.toString().startsWith("mouse"))return false;
		return fire(id,num,e);
	}
	
	/**
	   * 调用本窗体或组件的鼠标滚轮事件，其窗体id固定为this，注意滚轮的按下依然为mouseUp/mouseDown/click事件
	 * @param id 组件id或‘this’
	 * @param num 事件类型
	 * @param e 事件信息对象
	 * @return true-调用事件成功
	 */
	public boolean mouseWheelEventFire(String id,ActionEnum num,MouseWheelEvent e) {
		if(!num.toString().startsWith("mouseWheel"))return false;
		return fire(id,num,e);
	}
}
